﻿using System;
using System.Threading.Tasks;
using hello.csharp.common.Enums;
using hello.csharp.common.Interfaces.Logics;
using hello.csharp.common.Interfaces.Storages;
using hello.csharp.domain;
using hello.csharp.helper;
using NLog;

namespace hello.csharp.logic.authority
{
    public class AccountRegisterLogic : IAccountRegisterLogic
    {
        private static readonly ILogger _Logger = NLog.LogManager.GetCurrentClassLogger();
        private readonly IUserStorageRead _userRead;
        private readonly IUserStorageWrite _userWrite;
        private readonly IUserSnackStorageRead _userSnackRead;
        private readonly IUserSnackStorageWrite _userSnackWrite;

        public AccountRegisterLogic(IUserStorageRead userRead, 
            IUserStorageWrite userWrite, 
            IUserSnackStorageWrite userSnackWrite, 
            IUserSnackStorageRead userSnackRead)
        {
            _userRead = userRead;
            _userWrite = userWrite;
            _userSnackWrite = userSnackWrite;
            _userSnackRead = userSnackRead;
        }

        /// <summary>
        /// 用户注册
        /// </summary>
        /// <param name="nickname">昵称</param>
        /// <param name="email">邮箱</param>
        /// <param name="mobile">手机号码</param>
        /// <param name="pwSource">密码</param>
        /// <returns>用户注册是否成功</returns>
        public async Task<bool> RegisterAsync(string nickname, string email, string mobile, string pwSource)
        {
            var user = new User()
            {
                Nickname = nickname,
                Name = nickname,
                Email = email,
                Mobile = mobile,
            };

            try
            {
                await _userWrite.InsertAsync(user);
            }
            catch (Exception e)
            {
                _Logger.Error(e);
                return false;
            }
            var pepper = RandomHelper.GetRandomString(64);
            try
            {
                await _userSnackWrite.InsertAsync(new UserSnack()
                {
                    Id = user.Id,
                    NormalizedEmail = user.Email.ToUpper(),
                    NormalizedNickname = user.Nickname.ToUpper(),
                    Mobile = user.Mobile,
                    Pepper = pepper,
                    Value = CreateHash(pwSource, pepper)
                });
            }
            catch (Exception e)
            {
                _Logger.Error(e);
                return false;
            }

            await EmailHelper.SendUsableEmail(user.Id, user.Name, user.Email);
            return true;
        }

        /// <summary>
        /// 根据指定的密码和指定的密码盐值生成保存值
        /// </summary>
        /// <param name="pwSource">指定的密码</param>
        /// <param name="pepper">指定的盐值</param>
        /// <returns>用来持久化保存的值</returns>
        public string CreateHash(string pwSource, string pepper)
        {
            return PasswordHelper.CreateHash(pwSource, pepper);
        }

        /// <summary>
        /// 校验Email有效性。通过发送给用户邮件，用户点击邮件链接实现，邮件链接中保存有校验串。
        /// </summary>
        /// <param name="email">用户Email</param>
        /// <param name="value">校验串</param>
        /// <returns>Email是否有效</returns>
        public async Task<bool> SendUsableEmailAsync(string email, string value)
        {
            /*
             一些邮件链接供参考
             https://api.unity.com/v1/oauth2/verify-email?evc=dwiLrVqOTNg3MPCW7FOf5vFPSG672fsKOlDap07--8XwiqEW9_QQKKyZcStbdO7AKChv7ilogZbs3RR-HWt63889ig5SHPeGqIKPK6JC_Tc00efm001&locale=en_US
             https://hub.docker.com/account/confirm-email/9dc791c3681589f9df8ab9f8e042d9cbaaeedeb9/
             https://twitter.com/i/redirect?url=https%3A%2F%2Ftwitter.com%2Faccount%2Fconfirm_email%2Ferianknife%2FC8926-49FEB-141092%3Ft%3D1%26sig%3D1e3c5e51dd94a8d7de59a3cd0abaabed07d6926f%26al%3D1%26iid%3D33fb7c869fd5428c93a0e723f9110c34%26ac%3D1%26autoactions%3D1410928664%26uid%3D2773135287%26nid%3D18%2B308&t=1&sig=f0a36ff74d3e9d4c36c5724752bff3aa00384f1d&iid=33fb7c869fd5428c93a0e723f9110c34&uid=2773135287&nid=18+308
            */
            throw new NotImplementedException();
        }

        /// <summary>
        /// 校验手机号码有效性。通过发送给用户短信，用户输入短信验证码实现。
        /// </summary>
        /// <param name="mobile">用户手机号码</param>
        /// <param name="value">校验串</param>
        /// <returns>Email是否有效</returns>
        public async Task<bool> SendUsableMobileAsync(string mobile, string value)
        {
            throw new NotImplementedException();
        }

        /// <summary>
        /// 指定的唯一项是否平台唯一
        /// </summary>
        /// <param name="onlyItem">唯一项</param>
        /// <param name="value">唯一项的值</param>
        /// <returns>false表示平台已有该唯一项，true反之</returns>
        public async Task<bool> IsOnlyAsync(OnlyItem onlyItem, string value)
        {
            var isExist = await _userSnackRead.ExistByOnlyItemAsync(onlyItem, value);
            return isExist;
        }
    }
}
